package com.yixuan.mt.common.service.impl_mysql;

import com.fasterxml.jackson.core.JsonProcessingException;
import com.yixuan.mt.common.entity.User;
import com.yixuan.mt.common.exception.HttpBadRequestException;
import com.yixuan.mt.common.mapper.AuthMapper;
import com.yixuan.mt.common.properties.GlobalProperties;
import com.yixuan.mt.common.request.LoginRequest;
import com.yixuan.mt.common.service.AuthService;
import com.yixuan.mt.common.utitls.AdminTokenUtils;
import com.yixuan.mt.common.utitls.PoliciesCacheUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.security.crypto.bcrypt.BCryptPasswordEncoder;
import org.springframework.stereotype.Service;

import java.util.HashMap;
import java.util.Map;

@Service
public class AuthServiceMysqlImpl implements AuthService {

    private final BCryptPasswordEncoder passwordEncoder = new BCryptPasswordEncoder();
    @Autowired
    private GlobalProperties globalProperties;
    @Autowired
    private AuthMapper authMapper;
    @Autowired
    private PoliciesCacheUtils policiesCacheUtils;

    @Override
    public String login(LoginRequest loginRequest) throws JsonProcessingException {
        Integer userId = 0;
        // 特殊处理 admin
        if (loginRequest.getUsername().equals(globalProperties.getAdminDefaultUsername())) {
            if (!loginRequest.getPassword().equals(globalProperties.getAdminDefaultPassword())) {
                throw new HttpBadRequestException("用户名或密码错误！");
            }
        } else {
            // 根据用户名去获取（id和）密码
            User user = authMapper.selectIdPasswordByUsername(loginRequest.getUsername());
            // 如果用户不存在或密码不正确
            if (user == null || !passwordEncoder.matches(loginRequest.getPassword(), user.getPassword())) {
                throw new HttpBadRequestException("用户名或密码错误！");
            }
            userId = user.getId();
        }

        /*
         * 缓存用户权限。
         * 这里只有在用户id不为0时（admin）才去添加权限到缓存，
         * 在PoliciesCache初始化时已经缓存了默认管理员的权限。
         */
        if (!userId.equals(0)) {
            policiesCacheUtils.addUserPolicyCache(userId);
        }

        Map<String, Object> map = new HashMap<>();
        map.put("id", userId);
        return AdminTokenUtils.generateJwt(map);
    }
}
